/* eslint-disable */
import { saveAs } from 'file-saver'
import ExcelJs from 'exceljs/dist/exceljs'
import { base64Image } from './base64Image'
/**
 * 支持多sheet 导出excel
 * @param multiHeader 多行表头
 * @param headers 多sheet对应的表头
 * @param datas 数据，一个数组表示一个sheet中的数据
 * @param filename 文件名称
 * @param sheetnames sheet名称，数组格式的，数组中按次获取sheet名称
 * @param merges 合并单元格 一个数组表示一个sheet中的单元格合并情况，
 * 每个数组包含 合并单元格的top,left, bottom, right属性,
 * 分别为开始行，开始列，结束行，结束列
 * @param title 标题 一个数组表示一个sheet中的标题
 * @param showImage 是否插入图片
 * @param num 数字
 * @param autoWidth 自动列宽
 * @param bookType 文档类型
 */
export function export_json_to_excel_sheet({
  multiHeader = [],
  headers = [],
  datas = [],
  filename,
  sheetnames = [],
  merges = [],
  title = [],
  showImage = false,
  num,
  autoWidth = true,
  bookType = 'xlsx'
} = {}) {
  // 创建一个工作簿
  const workbook = new ExcelJs.Workbook()
  // 遍历数据
  for (let tmp = 0; tmp <= datas.length - 1; tmp++) {
    // 获取数据
    const data = datas[tmp]
    // 添加表头, 合并表头的数据
    const header = headers[tmp]
    // 表头所在行号
    let headerRowNum = 1
    data.unshift(header)
    // 多行标头
    for (let i = multiHeader.length - 1; i > -1; i--) {
      data.unshift(multiHeader[i])
    }
    // 第二行数字，待更改
    if (![null, undefined].includes(num)) {
      headerRowNum++;
      const numData = []
      header.map((item, index) => {
        if (index !== 0) {
          numData.unshift('')
        } else {
          numData.unshift(num)
        }
      })
      data.unshift(numData)
    }
    // 标题
    if (title && title[tmp]) {
      headerRowNum++;
      const titleData = []
      header.map((item, index) => {
        if (index !== (header.length - 1)) {
          titleData.unshift('')
        } else {
          titleData.unshift(title[tmp])
        }
      })
      data.unshift(titleData)
    }
    // 获取sheetname
    var wsName = sheetnames[tmp]
    const worksheet = workbook.addWorksheet(wsName)
    worksheet.addRows(data)

    if (title && title[tmp]) {
      // 合并标题 按开始行，开始列，结束行，结束列合并
      worksheet.mergeCells(1, 1, 1, header.length)
    }
    // 表头合并
    // if (headerMerge) {
    //   const mergeHeader = headerSpan(header)
    //   mergeHeader.map((value, index, array) => {
    //     if (value > 1) {
    //       for (let i = 0; i <= worksheet._lastRowNumber - headerRowNum; i++) {
    //         dealMergeData(worksheet, {
    //           top: i,
    //           bottom: i,
    //           left: index + 1,
    //           right: value + index
    //         }, headerRowNum)
    //         worksheet.mergeCells(
    //           i + headerRowNum,
    //           index + 1,
    //           i + headerRowNum,
    //           value + index)
    //       }
    //     }
    //   })
    // }
    // 处理合并单元格的数据
    if (merges && merges[tmp]) {
      const merge = merges[tmp]
      merge.map((item) => {
      dealMergeData(worksheet, item, headerRowNum, false)
      // 合并单元格
      worksheet.mergeCells(
          headerRowNum + item.top,
          item.left,
          headerRowNum + item.bottom,
          item.right)
      })
    }
    // 行居中
    rowCenter(worksheet, 1 + multiHeader.length, data.length, headerRowNum)
    // 自动处理列宽
    if (autoWidth) {
      /* 设置worksheet每列的最大宽度*/
      const columnWidth = data.map(row => row.map(val => {
        /* 先判断是否为null/undefined*/
        if (val == null) {
          return {
            'width': 10
          }
        }
        /* 再判断是否为中文*/
        else if (val.toString().charCodeAt(0) > 255) {
          return {
            'width': val.toString().length * 3
          }
        } else {
          return {
            'width': val.toString().length *2.5
          }
        }
      }))
      
      /* 以第一行为初始值*/
      const result = columnWidth[0]
      result[0].width = 35;
      console.log(result)
      for (let i = 1; i < columnWidth.length; i++) {
        for (let j = 0; j < columnWidth[i].length; j++) {
          if (result[j]['width'] < columnWidth[i][j]['width']) {
            result[j]['width'] = columnWidth[i][j]['width']
          }
        }
      }
      // 设置列宽
      colWidth(worksheet, result)
      if (showImage) {
        const imageType = base64Image.slice(base64Image.indexOf('/') + 1, base64Image.indexOf('base64') - 1)
        const imageId = workbook.addImage({
          base64: base64Image,
          extension: imageType
        })
        // 设置图片位置，默认在第二行，第一列
        setImage({
          arg_ws: worksheet,
          imageId })
      }
      }

  }

  /**
   * 得到表头合并信息
   * @param header 表头数据
   * @returns {*[]} 返回包含重复信息的数组，index对应表头的index，value对应重复次数
   */
  function headerSpan(header) {
    let span = [...header]
    const spanIndex = []
    header.map((value, index, array) =>{
      span[index] = 1
      array.forEach((val, i) => {
        if (val === value && i !== index && !spanIndex.includes(i)) {
          spanIndex.push(index)
          span[index]++
        }
      })
    })
    span.map((value, index, array) => {
      if (value > 1 ) {
        for (let i = index + 1; i < index + value; i++) {
          array[i] = index - i
        }
      }
    })
    return span
  }
  /**
   * 处理要合并的数据
   * @param arg_ws worksheet
   * @param mergeItem 合并单元格信息
   * @param headerRowNum 表头行号
   * @param option 选择合并时数据是拼接还是去单个值
   */
  function dealMergeData(arg_ws, mergeItem, headerRowNum, option = true) {
    let mergeValue = arg_ws.getCell(
      headerRowNum + mergeItem.top,
      mergeItem.left).value
    let mergeArr = []
    if (option){
      // 处理合并单元格的数据，以由左到右，自上而下的顺序选择第一个有数据的单元格作为合并单元格的数据
      if (!mergeValue) {
        for (let i = headerRowNum + mergeItem.top;i <= headerRowNum + mergeItem.bottom; i++) {
          for (let j = mergeItem.left;j <= mergeItem.right; j++) {
            if (!mergeValue && arg_ws.getCell(i,j).value) {
              mergeValue = arg_ws.getCell(i,j).value
            }
          }
        }
        arg_ws.getCell(
          headerRowNum + mergeItem.top,
          mergeItem.left).value = mergeValue
      }
    } else {
      // 拼接全部数据
      for (let i = headerRowNum + mergeItem.top;i <= headerRowNum + mergeItem.bottom; i++) {
        for (let j = mergeItem.left;j <= mergeItem.right; j++) {
          mergeArr.push(arg_ws.getCell(i,j).value)
        }
      }
      mergeValue = mergeArr.join("")
      arg_ws.getCell(
        headerRowNum + mergeItem.top,
        mergeItem.left).value = mergeValue
    }
  }
  /**
   *  设置start-end行单元格水平垂直居中/添加边框和背景颜色
   * @param arg_ws workSheet 参数
   * @param arg_start 开始行
   * @param arg_end 结束结束行
   * @param headerRowNum 表头行号
   */
  function rowCenter(arg_ws, arg_start, arg_end, headerRowNum) {
    let i = arg_start
    for (; i <= arg_end; i++) {
      arg_ws.findRow(i).alignment = { vertical: 'middle', horizontal: 'center', wrapText: true }
      arg_ws.findRow(i).eachCell({ includeEmpty: true },function(cell, index) {
        // 循环 row 中的　cell，给每个 cell添加边框
        cell.font = {
          size: 14,
          name: '宋体',
          sz: '14',
          bold: false
        }
        // 设置标题背景颜色和边框
        if (i === headerRowNum) {
          cell.fill = {
            type: 'pattern',
            pattern: 'solid',
            fgColor: { argb: 'FF999999' }
          }
          cell.border = {
            top: { style: 'thin' },
            left: { style: 'thin' },
            bottom: { style: 'thin' },
            right: { style: 'thin' }
          }
        }
      })
    }
  }
  // 设置　start-end 列的宽度
  /**
   * 设置行宽
   * @param arg_ws workSheet
   * @param arg_cols 列数组
   */
  function colWidth(arg_ws, arg_cols) {
    for (const i in arg_cols) {
      arg_ws.getColumn(parseInt(i) + 1).width = arg_cols[i].width
    }
  }

  /**
   * 设置图片大小和位置
   * @param arg_ws workSheet 参数
   * @param arg_row 图片所在行
   * @param arg_col 图片所在列
   * @param imageId
   */
  function setImage({
    arg_ws,
    arg_row = 1,
    arg_col = 1,
    imageId } = {}) {
    const col = arg_ws.getColumn(arg_col);
    const row = arg_ws.getRow(arg_row);
    row.height = 20
    // 计算图片高度和宽度
    // let imageWidth =  col.width * 8;
    // let imageHeight = (96 / 72) * row.height
    let imageWidth =  col.width * 7.2;
    let imageHeight = 47;
    arg_ws.addImage(imageId, {
      tl: { col: arg_col - 1 , row: arg_row - 1 },
      ext: { width: imageWidth, height: imageHeight },
      editAs: 'undefined'
    })
  }
  // 保存设置
  workbook.xlsx.writeBuffer().then(buffer => {
    saveAs(new Blob([buffer], {
      type: 'application/octet-stream'
    }), `${filename}.${bookType}`)
  })
}

